package com.ruoyi.framework.aspectj;

import com.ruoyi.common.annotation.SearchLog;
import com.ruoyi.common.enums.HttpMethod;
import com.ruoyi.common.utils.ServletUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.system.domain.SysOperLog;
import org.apache.commons.lang.builder.ToStringBuilder;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.aspectj.lang.reflect.MethodSignature;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.servlet.HandlerMapping;

import java.lang.reflect.Method;
import java.util.Map;
import java.util.logging.LogRecord;

/**
 * 检索日志记录处理
 *
 * @author ruoyi
 */
@Aspect
@Component
public class SearchLogAspect {

    private static final Logger LOGGER = LoggerFactory.getLogger(SearchLogAspect.class);

    private final ThreadLocal<Long> threadLocal=new ThreadLocal<>();

    @Pointcut("@annotation(com.ruoyi.common.annotation.SearchLog)")
    public void annotationPointcut(){

    }

    @Before("annotationPointcut()")
    public void beforePointcut(JoinPoint joinPoint) {
        // 此处进入到方法前  可以实现一些业务逻辑
        MethodSignature methodSignature=(MethodSignature)joinPoint.getSignature();
        Method method=methodSignature.getMethod();
        SearchLog annotation = method.getAnnotation(SearchLog.class);
        LOGGER.info(parseParames(joinPoint.getArgs()));
        if (annotation!=null){
            threadLocal.set(System.currentTimeMillis());
        }
    }



    @Around("annotationPointcut()")
    public Object Interceptor(ProceedingJoinPoint pjp){
        Object result = null;
        try {
            result =pjp.proceed();
        } catch (Throwable e) {
            e.printStackTrace();
        }
        return result;
    }


    @After("annotationPointcut()")
    public void afterPointcut(JoinPoint joinPoint) {
        // 此处执行方法后  可以实现一些业务逻辑
        Method method=((MethodSignature)joinPoint.getSignature()).getMethod();
        SearchLog annotation = method.getAnnotation(SearchLog.class);
        if (annotation!=null){
            Long startTime=threadLocal.get();
            Long endTime=System.currentTimeMillis();
            Long costTime=endTime-startTime;

            String requestUri = ServletUtils.getRequest().getRequestURI();
            String className = joinPoint.getTarget().getClass().getName(); //类路径
            String methodName = joinPoint.getSignature().getName(); //方法名
            String methodFullPath = className+"."+methodName+"()";
            LOGGER.info("requestUri({}) methodFullPath({}) methodName({}) methodDesc({}) ==> 花费时间 {}ms",requestUri, methodFullPath, methodName, "查询",costTime);
        }

    }

    /**
     * 在切入点return内容之后切入内容（可以用来对处理返回值做一些加工处理）
     * @param joinPoint
     */
    @AfterReturning("annotationPointcut()")
    public void afterReturningPointcut(JoinPoint joinPoint) {
    }

    private String parseParames(Object[] parames){
        if(null == parames || parames.length <= 0 || parames.length>1024){
            return "";
        }
        StringBuffer param = new StringBuffer("传入参数[{}] ");
        for(Object obj : parames){
            param.append(ToStringBuilder.reflectionToString(obj)).append(" ");
        }
        return param.toString();
    }
}
